<html>
    <head>
    <link rel="stylesheet" href="lmm.css" type="text/css" />
    </head>
<body class="lmm">
<!-- This file is part of the Lisp Machine manual.	-*-Text-*- -->

<!-- Still need explanation of states in general, and of RG-style error checking. -->
<!-- Need examples! -->

<div class='chapter' id='13'>13. Stack Groups</div><p class='cindent'><!-- "stack" -->

	A <!-- open: 1, close: 0 --><font class="italic">stack</font><!-- open: 1, close: 1 --> <!-- MATCHED MATCHED MATCHED --> (usually abbreviated "SG") is a type of Lisp
object useful for implementation of certain advanced control structures
such as coroutines and generators.  A stack represents a
computation and its internal state, including the Lisp stack.
At any time, the computation being
performed by the Lisp Machine is associated with one stack,
called the <!-- open: 2, close: 1 --><font class="italic">current</font><!-- open: 2, close: 2 --> <!-- MATCHED MATCHED MATCHED --> or <!-- open: 3, close: 2 --><font class="italic">running</font><!-- open: 3, close: 3 --> <!-- MATCHED MATCHED MATCHED --> stack.  The operation of
making some stack be the current stack is called a
<!-- open: 4, close: 3 --><font class="italic">resumption</font><!-- open: 4, close: 4 --> <!-- MATCHED MATCHED MATCHED --> or a <!-- open: 5, close: 4 --><font class="italic">stack switch</font><!-- open: 5, close: 5 --> <!-- MATCHED MATCHED MATCHED -->; the running stack is
said to have <!-- open: 6, close: 5 --><font class="italic">resumed</font><!-- open: 6, close: 6 --> <!-- MATCHED MATCHED MATCHED --> the new stack.  The <!-- open: 7, close: 6 --><font class="italic">resume</font><!-- open: 7, close: 7 --> <!-- MATCHED MATCHED MATCHED --> operation
has two parts: first, the state of the running computation is saved
away inside the current stack, and secondly the state saved in
the new stack is restored, and the new stack is made
current.  Then the computation of the new stack resumes its
course.

	The stack remembers all functions which
were active at the time of the resumption (that is, the running
function, its caller, its caller's caller, etc.), and where
in each function the computation was up to.  In other words,
the entire control stack (or regular pdl) is saved.  In addition,
the bindings that were present are saved also; that is, the environment
stack (or special pdl) is saved.  When the state of the current
stack is saved away, all of its bindings are undone,
and when the state is restored, the bindings are put back.
Note that although bindings are temporarily undone, unwind-protect
handlers are <!-- open: 8, close: 7 --><font class="italic">not</font><!-- open: 8, close: 8 --> <!-- MATCHED MATCHED MATCHED --> run (see <!-- open: 9, close: 8 --><font class="lisp">let-globally</font><!-- open: 9, close: 9 --> <!-- MATCHED MATCHED MATCHED -->).

	There are several ways that a resumption can happen.  First of all,
there are several Lisp functions, described below, which resume some
other stack.  When some stack (call it <!-- open: 10, close: 9 --><font class="lisp">c</font><!-- open: 10, close: 10 --> <!-- MATCHED MATCHED MATCHED -->) calls such a
function, it is suspended in the state of being in the middle of a call
to that function.  When someone eventually resumes <!-- open: 11, close: 10 --><font class="lisp">c</font><!-- open: 11, close: 11 --> <!-- MATCHED MATCHED MATCHED -->, the function
will return.  The arguments to these functions and the returned values
can therefore be used to pass information back and forth between stack
groups.  Secondly, if an error is signalled, the current stack
resumes an error handler stack, which handles the error in some
way.  Thirdly, a <!-- open: 12, close: 11 --><font class="italic">sequence break</font><!-- open: 12, close: 12 --> <!-- MATCHED MATCHED MATCHED --> can happen, which  transfers
control to a special stack called the <!-- open: 13, close: 12 --><font class="italic">scheduler</font><!-- open: 13, close: 13 --> <!-- MATCHED MATCHED MATCHED --> (see <font color='red'>LINK:(</font>scheduler)).

	Note: the following discussion of resumers is incomplete, and the
way they work is being changed anyway.

<p class='cindent' id='stack-group'><!-- resumer -->
	Each stack has a <!-- open: 14, close: 13 --><font class="italic">resumer</font><!-- open: 14, close: 14 --> <!-- MATCHED MATCHED MATCHED -->.  <!-- open: 15, close: 14 --><font class="italic">c</font><!-- open: 15, close: 15 --> <!-- MATCHED MATCHED MATCHED -->'s resumer is some other
stack, which essentially is the last stack to resume <!-- open: 16, close: 15 --><font class="italic">c</font><!-- open: 16, close: 16 --> <!-- MATCHED MATCHED MATCHED -->.
This is not completely right, however, because some resume-forms set the
resumed stack's resumer, and some don't.  So <!-- open: 17, close: 16 --><font class="italic">c</font><!-- open: 17, close: 17 --> <!-- MATCHED MATCHED MATCHED -->'s resumer is actually
the last stack to resume <!-- open: 18, close: 17 --><font class="italic">c</font><!-- open: 18, close: 18 --> <!-- MATCHED MATCHED MATCHED --> by means of one of the types of
resume-form which does set the resumer.

<div class='defvar' id='si:%current-stack-previous-stack'><font class='exdent'><font class='funcname' id='si:%current-stack-previous-stack'>si:%current-stack-previous-stack</font><font class="italic"> Variable</font><br></font><!-- end font_exdent -->The binding of this variable is the resumer of the current stack.
</div>

	There are currently four kinds of resume-forms:
<table>
<tr valign='top'>
<td><font class='lisp'> 1)</font></td><td>If <!-- open: 19, close: 18 --><font class="italic">c</font><!-- open: 19, close: 19 --> <!-- MATCHED MATCHED MATCHED --> calls <!-- open: 20, close: 19 --><font class="italic">s</font><!-- open: 20, close: 20 --> <!-- MATCHED MATCHED MATCHED --> as a function with an argument <!-- open: 21, close: 20 --><font class="italic">x</font><!-- open: 21, close: 21 --> <!-- MATCHED MATCHED MATCHED -->, then <!-- open: 22, close: 21 --><font class="italic">s</font><!-- open: 22, close: 22 --> <!-- MATCHED MATCHED MATCHED --> is resumed,
and the object transmitted is <!-- open: 23, close: 22 --><font class="italic">x</font><!-- open: 23, close: 23 --> <!-- MATCHED MATCHED MATCHED -->.  <!-- open: 24, close: 23 --><font class="italic">s</font><!-- open: 24, close: 24 --> <!-- MATCHED MATCHED MATCHED -->'s resumer is now <!-- open: 25, close: 24 --><font class="italic">c</font><!-- open: 25, close: 25 --> <!-- MATCHED MATCHED MATCHED -->.
</td></tr>
<tr valign='top'>
<td><font class='lisp'> 2)</font></td><td>If <!-- open: 26, close: 25 --><font class="italic">c</font><!-- open: 26, close: 26 --> <!-- MATCHED MATCHED MATCHED --> evaluates <!-- open: 27, close: 26 --><font class="lisp">(stack-return <!-- open: 28, close: 26 --><font class="italic">x</font><!-- open: 28, close: 27 -->)</font><!-- open: 28, close: 28 --> <!-- MATCHED MATCHED MATCHED -->, then its resumer
is resumed, and the object transmitted is <!-- open: 29, close: 28 --><font class="italic">x</font><!-- open: 29, close: 29 --> <!-- MATCHED MATCHED MATCHED -->.  The resumer's resumer
is not affected.
</td></tr>
<tr valign='top'>
<td><font class='lisp'> 3)</font></td><td>If <!-- open: 30, close: 29 --><font class="italic">c</font><!-- open: 30, close: 30 --> <!-- MATCHED MATCHED MATCHED --> evaluates <!-- open: 31, close: 30 --><font class="lisp">(stack-resume <!-- open: 32, close: 30 --><font class="italic">s</font><!-- open: 32, close: 31 --> <!-- open: 33, close: 31 --><font class="italic">x</font><!-- open: 33, close: 32 -->)</font><!-- open: 33, close: 33 --> <!-- MATCHED MATCHED MATCHED -->, then
<!-- open: 34, close: 33 --><font class="italic">c</font><!-- open: 34, close: 34 --> <!-- MATCHED MATCHED MATCHED --> is resumed, and the object transmitted is <!-- open: 35, close: 34 --><font class="italic">x</font><!-- open: 35, close: 35 --> <!-- MATCHED MATCHED MATCHED -->.  <!-- open: 36, close: 35 --><font class="italic">c</font><!-- open: 36, close: 36 --> <!-- MATCHED MATCHED MATCHED -->'s resumer
is not affected.  (This is not currently implemented.)
</td></tr>
<tr valign='top'>
<td><font class='lisp'> 4)</font></td><td>If the initial function of <!-- open: 37, close: 36 --><font class="italic">c</font><!-- open: 37, close: 37 --> <!-- MATCHED MATCHED MATCHED --> attempts to return a value <!-- open: 38, close: 37 --><font class="italic">x</font><!-- open: 38, close: 38 --> <!-- MATCHED MATCHED MATCHED -->,
the regular kind of Lisp function return cannot take place, since
the function did not have any caller (it got there when the stack
was initialized).  So instead of returning, its resumer is resumed, and
the value transmitted is <!-- open: 39, close: 38 --><font class="italic">x</font><!-- open: 39, close: 39 --> <!-- MATCHED MATCHED MATCHED -->.  The resumer's resumer is not affected.
<!-- open: 40, close: 39 --><font class="italic">c</font><!-- open: 40, close: 40 --> <!-- MATCHED MATCHED MATCHED --> is left in a state from which it cannot be resumed again; any
attempt to resume it would signal an error.
</td></tr><!-- item_ --></table><!-- end table -->

	There is one other way a stack can be resumed.  If the
running stack <!-- open: 41, close: 40 --><font class="italic">c</font><!-- open: 41, close: 41 --> <!-- MATCHED MATCHED MATCHED --> gets a microcode trap, then the error handler
stack is resumed.  The object transmitted is <!-- open: 42, close: 41 --><font class="lisp">nil</font><!-- open: 42, close: 42 --> <!-- MATCHED MATCHED MATCHED -->, and the
error handler's resumer is set to <!-- open: 43, close: 42 --><font class="italic">c</font><!-- open: 43, close: 43 --> <!-- MATCHED MATCHED MATCHED -->.  This kind of resuming will
only happen to the error handler, so regular programs should not see
it.

<div class='section' id='13.1'>13.1 What is Going On Inside</div>
	The stack itself holds a great deal of state information.
First of all, it contains the control stack, or "regular PDL".  The
control stack is what you are shown by the backtracing commands of the
error handler (currently the Control-B and Meta-B commands); it
remembers the function which is running, its caller, its caller's
caller, and so on, and remembers the point of execution of each function
(i.e. the "return addresses" of each function).
Secondly, it contains the environment stack, or "special PDL".
This contains all of the values saved by <!-- open: 44, close: 43 --><font class="lisp">lambda</font><!-- open: 44, close: 44 --> <!-- MATCHED MATCHED MATCHED -->-binding.  Finally,
it contains various internal state information (contents of machine
registers and so on).

	When one stack resumes a second, the first thing that
happens is that (some of) the state of the processor is saved in the
first stack.  Next, all of the bindings in effect are undone;
each stack has its own environment, and the bindings done in one
stack do not affect another stack at all.  Then the second
stack's bindings are restored, its machine state is restored, and
the second stack proceeds from where it left off.  While these
things are happening, the transmitted object is passed into the second
stack, and optionally the second stack's resumer is made
to be the first stack.


<!-- More narrative here. -->

<div class='defvar' id='si:%current-stack'><font class='exdent'><font class='funcname' id='si:%current-stack'>si:%current-stack</font><font class="italic"> Variable</font><br></font><!-- end font_exdent -->The value of <!-- open: 45, close: 44 --><font class="lisp">si:%current-stack</font><!-- open: 45, close: 45 --> <!-- MATCHED MATCHED MATCHED --> is the stack which is
currently running.  A program can use this variable to get its hands
on its own stack.
</div>

<div class='defun' id='make-stack-group'>
  <font class='exdent'>
    <font class='funcname'>make-stack-group </font>
    <font class='italic' color='purple'>name &optional options</font>
  </font><br>
This creates and returns a new stack.  <!-- open: 46, close: 45 --><font class="italic">name</font><!-- open: 46, close: 46 --> <!-- MATCHED MATCHED MATCHED --> may be any symbol; it is used
to identify and print the stack.  Each option is a keyword followed by
a value for that option; any number of options may be given, including zero.
The options are not too useful; most calls to
<!-- open: 47, close: 46 --><font class="lisp">make-stack</font><!-- open: 47, close: 47 --> <!-- MATCHED MATCHED MATCHED --> don't have any options at all.
The options are:
<table>
<tr valign='top'>
<td><font class='lisp'> :sg-area</font></td><td>The area in which to create the stack structure itself.
Defaults to <!-- open: 48, close: 47 --><font class="lisp">default-array-area</font><!-- open: 48, close: 48 --> <!-- MATCHED MATCHED MATCHED -->.
</td></tr>
<tr valign='top'><td colspan='2'><font class='lisp'> :regular-pdl-area</font></td><td><!-- empty --></td></tr>
<tr><td><!-- empty title --></td><td>The area in which to create the regular PDL.  Note that this
may not be any area; only certain areas may hold regular PDL,
because accessing a regular PDL as memory must go through special
microcode which checks an internal cache called the <!-- open: 49, close: 48 --><font class="italic">pdl buffer</font><!-- open: 49, close: 49 --> <!-- MATCHED MATCHED MATCHED -->.
<!-- Just what needs to be true of the area? -->
Defaults to <!-- open: 50, close: 49 --><font class="lisp">error-linear-pdl-area</font><!-- open: 50, close: 50 --> <!-- MATCHED MATCHED MATCHED -->.
</td></tr>
<tr valign='top'><td colspan='2'><font class='lisp'> :special-pdl-area</font></td><td><!-- empty --></td></tr>
<tr><td><!-- empty title --></td><td>The area in which to create the special PDL.
Defaults to <!-- open: 51, close: 50 --><font class="lisp">default-array-area</font><!-- open: 51, close: 51 --> <!-- MATCHED MATCHED MATCHED -->.
</td></tr>
<tr valign='top'><td colspan='2'><font class='lisp'> :regular-pdl-size</font></td><td><!-- empty --></td></tr>
<tr><td><!-- empty title --></td><td>Length of the regular PDL to be created.  Defaults to 3000.
</td></tr>
<tr valign='top'><td colspan='2'><font class='lisp'> :special-pdl-size</font></td><td><!-- empty --></td></tr>
<tr><td><!-- empty title --></td><td>Length of the special PDL to be created.  Defaults to 400.
</td></tr>
<tr valign='top'>
<td><font class='lisp'> :car-sym-mode</font></td><td>The "error mode" which determines the action taken when there
is an attempt to apply <!-- open: 52, close: 51 --><font class="lisp">car</font><!-- open: 52, close: 52 --> <!-- MATCHED MATCHED MATCHED --> to a symbol.  This, and the other
"error mode" options, are documented with the fucntions <!-- open: 53, close: 52 --><font class="lisp">car</font><!-- open: 53, close: 53 --> <!-- MATCHED MATCHED MATCHED -->
and <!-- open: 54, close: 53 --><font class="lisp">cdr</font><!-- open: 54, close: 54 --> <!-- MATCHED MATCHED MATCHED -->.  Defaults to <!-- open: 55, close: 54 --><font class="lisp">1</font><!-- open: 55, close: 55 --> <!-- MATCHED MATCHED MATCHED -->.
</td></tr>
<tr valign='top'>
<td><font class='lisp'> :car-num-mode</font></td><td>As above, for applying <!-- open: 56, close: 55 --><font class="lisp">car</font><!-- open: 56, close: 56 --> <!-- MATCHED MATCHED MATCHED --> to a number.  Defaults to 0.
</td></tr>
<tr valign='top'>
<td><font class='lisp'> :cdr-sym-mode</font></td><td>As above, for applying <!-- open: 57, close: 56 --><font class="lisp">cdr</font><!-- open: 57, close: 57 --> <!-- MATCHED MATCHED MATCHED --> to a symbol.  Defaults to 1.
</td></tr>
<tr valign='top'>
<td><font class='lisp'> :cdr-num-mode</font></td><td>As above, for applying <!-- open: 58, close: 57 --><font class="lisp">cdr</font><!-- open: 58, close: 58 --> <!-- MATCHED MATCHED MATCHED --> to a number.  Defaults to 0.
</td></tr>
<tr valign='top'><td colspan='2'><font class='lisp'> :swap-sv-on-call-out</font></td><td><!-- empty --></td></tr>
<tr><td><!-- empty title --></td><td></td></tr>
<tr valign='top'><td colspan='2'><font class='lisp'> :swap-sv-of-sg-that-calls-me</font></td><td><!-- empty --></td></tr>
<tr><td><!-- empty title --></td><td></td></tr>
<tr valign='top'>
<td><font class='lisp'> :trap-enable</font></td><td>This determines what to do if a microcode error occurs.
If it is <!-- open: 59, close: 58 --><font class="lisp">1</font><!-- open: 59, close: 59 --> <!-- MATCHED MATCHED MATCHED --> the system tries to handle the error;
if it is <!-- open: 60, close: 59 --><font class="lisp">0</font><!-- open: 60, close: 60 --> <!-- MATCHED MATCHED MATCHED --> the machine halts.  Defaults to 1.
</td></tr>
<tr valign='top'>
<td><font class='lisp'> :safe</font></td><td>If <!-- open: 61, close: 60 --><font class="lisp">1</font><!-- open: 61, close: 61 --> <!-- MATCHED MATCHED MATCHED --> (the default), a strict call-return discipline among
stacks is enforced.  If <!-- open: 62, close: 61 --><font class="lisp">0</font><!-- open: 62, close: 62 --> <!-- MATCHED MATCHED MATCHED -->, no restriction on stack
switching is imposed.
<!-- I could explain this a lot better if I understood it. -->
</td></tr><!-- item_ --></table><!-- end table -->

</div>

<div class='defun' id='stack-group-preset'>
  <font class='exdent'>
    <font class='funcname'>stack-group-preset </font>
    <font class='italic' color='purple'>stack-group function &rest arguments</font>
  </font><br>
This sets up <!-- open: 63, close: 62 --><font class="italic">stack</font><!-- open: 63, close: 63 --> <!-- MATCHED MATCHED MATCHED --> so that when it is resumed,
<!-- open: 64, close: 63 --><font class="italic">function</font><!-- open: 64, close: 64 --> <!-- MATCHED MATCHED MATCHED --> will be applied to <!-- open: 65, close: 64 --><font class="italic">arguments</font><!-- open: 65, close: 65 --> <!-- MATCHED MATCHED MATCHED --> within the stack.
Both stacks are made empty.
<!-- open: 66, close: 65 --><font class="lisp">stack-preset</font><!-- open: 66, close: 66 --> <!-- MATCHED MATCHED MATCHED --> is used to initialize a stack just after it is made,
but it may be done to any stack at any time.
</div>

<div class='defun' id='stack-group-return'>
  <font class='exdent'>
    <font class='funcname'>stack-group-return </font>
    <font class='italic' color='purple'>x</font>
  </font><br>
Let <!-- open: 67, close: 66 --><font class="italic">s</font><!-- open: 67, close: 67 --> <!-- MATCHED MATCHED MATCHED --> be the current stack's resumer;
<!-- open: 68, close: 67 --><font class="lisp">stack-return</font><!-- open: 68, close: 68 --> <!-- MATCHED MATCHED MATCHED --> will resume <!-- open: 69, close: 68 --><font class="italic">s</font><!-- open: 69, close: 69 --> <!-- MATCHED MATCHED MATCHED -->, transmitting
the value <!-- open: 70, close: 69 --><font class="italic">x</font><!-- open: 70, close: 70 --> <!-- MATCHED MATCHED MATCHED -->.  <!-- open: 71, close: 70 --><font class="italic">s</font><!-- open: 71, close: 71 --> <!-- MATCHED MATCHED MATCHED -->'s resumer is not affected.
</div>

<div class='defun' id='stack-group-resume'>
  <font class='exdent'>
    <font class='funcname'>stack-group-resume </font>
    <font class='italic' color='purple'>s x</font>
  </font><br>
<!-- open: 72, close: 71 --><font class="lisp">stack-resume</font><!-- open: 72, close: 72 --> <!-- MATCHED MATCHED MATCHED -->
will resume <!-- open: 73, close: 72 --><font class="italic">s</font><!-- open: 73, close: 73 --> <!-- MATCHED MATCHED MATCHED -->, transmitting the object <!-- open: 74, close: 73 --><font class="italic">x</font><!-- open: 74, close: 74 --> <!-- MATCHED MATCHED MATCHED -->.  <!-- open: 75, close: 74 --><font class="italic">s</font><!-- open: 75, close: 75 --> <!-- MATCHED MATCHED MATCHED -->'s
resumer is not affected.  This function is not currently implemented.
</div>

<!-- Add some discussion of the screws Gosper encountered.  Discuss how -->
<!-- stack-groups relate to variables, environments, conditions, throws, etc. -->

<!-- eof -->
</body>
</html>

